package com.herohead;

import java.io.IOException;

import redis.clients.jedis.Jedis;
import redis.clients.jedis.Transaction;

import com.herohead.redis.RedisKeys;
import com.herohead.redis.RedisVars;


public class WorkerThreadV3 implements Runnable {


	public static String getScore(Jedis jd,String hash, String key) {
		return jd.hget(hash, key);
	}
	String tempkey;
	Long threadProcessID;
	String threadEndTime;

	String threadStartTime;
	private final String command;
	private final String queID;
	private final String cloneName;
	private final boolean debug;

	Process p;


	Transaction tx;


	public WorkerThreadV3(String s,String queIDs,String cName,boolean debug){
		this.command=s;
		this.queID=queIDs;
		this.cloneName=cName;
		this.debug = debug;
	}

	private void processCommand() throws InterruptedException, IOException {


		//Jedis jd = new Jedis("localhost");


		//GetRedisServer grs = new GetRedisServer();
		//Jedis jd = new Jedis(grs.getRedisHost());
		RedisVars.redisHost = "localhost";
		final Jedis jd = new Jedis(RedisVars.redisHost);
		String[] ssidInCommand;

		try {
			threadStartTime = (Misc.getTimestamp());
			System.out.println(threadStartTime + " Starting : "+ command);


			//String[] ssidInCommand = command.split("-S")[1].split(" ");
			ssidInCommand = command.split("-S")[1].trim().split(" ");
			//for (String ssid : ssidInCommand) {
			//	System.out.println("Here is the list of ssid found in ssidINCommand " + ssid);
			//}

			threadProcessID = jd.incr("thread:cnt");
			jd.hset(RedisKeys.hashProdThreadRunningProcessID,queID, getScore(jd,RedisKeys.hashProdThreadQueuedProcessID,queID));
			jd.zincrby(RedisKeys.sListProdCloneQueuedSize, Double.parseDouble(getScore(jd,RedisKeys.hashProdThreadQueuedProcessID,queID)) * -1,cloneName );
			jd.zincrby(RedisKeys.sListProdCloneRunningSize, Double.parseDouble(getScore(jd,RedisKeys.hashProdThreadQueuedProcessID,queID)),cloneName );
			jd.hdel(RedisKeys.hashProdThreadQueuedProcessID,queID);
			jd.rpush(RedisKeys.listProdThreadRunning, String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + command);
			//jd.hdel(hashProdThreadQueuedProcessID,queID);
			tempkey = String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + command;
			jd.close();
			// Run command

			if (debug) {
				p = Runtime.getRuntime().exec("cmd /c start /wait " + command);
			} else {
				p = Runtime.getRuntime().exec(command);
			}

			System.out.println("Waiting for clone to finish ...");

			p.waitFor();



			jd.connect();
			threadEndTime = (Misc.getTimestamp());

			if (p.exitValue() == 0) {
				//Jedis jdpl = new Jedis(grs.getRedisHost());
				//tx = jdpl.multi();
				//System.out.println("Trying to delete from ssidNotCloned");
				for (String ssid : ssidInCommand) {
					jd.srem(RedisKeys.setProdSSIDNotCloned, ssid.trim());
					//System.out.println("Trying to delete " +  ssid + " the ssid found in ssidInCommad");

				}

				//tx.exec();
				//jdpl.close();

				jd.hset(RedisKeys.listProdThreadCompletedProcessID,queID, getScore(jd,RedisKeys.hashProdThreadRunningProcessID,queID));
				jd.hdel(RedisKeys.hashProdThreadRunningProcessID,queID);
				jd.lrem(RedisKeys.listProdThreadRunning, 1, tempkey);
				jd.rpush(RedisKeys.listProdThreadCompleted, String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + threadEndTime + "|" + command);
				System.out.println(threadEndTime + " Ending : "+ command);
			} else {
				jd.hset(RedisKeys.hashProdThreadFailedProcessID,queID, getScore(jd,RedisKeys.hashProdThreadRunningProcessID,queID));
				jd.hdel(RedisKeys.hashProdThreadRunningProcessID,queID);

				jd.lrem(RedisKeys.listProdThreadRunning, 1, tempkey);
				jd.rpush(RedisKeys.listProdThreadFailed, String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + threadEndTime + "|" + command);
				System.out.println(threadEndTime + " Failed : "+ command);
			}

		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			jd.close();
		}


		Runtime.getRuntime().addShutdownHook(new Thread() {

			@Override
			public void run() {
				RedisVars.redisHost = "localhost";
				final Jedis jd = new Jedis(RedisVars.redisHost);

				p.destroy();
				//Thread.currentThread().stop();
				System.out.println("Program stoped");
				jd.hset(RedisKeys.hashProdThreadFailedProcessID,queID, getScore(jd,RedisKeys.hashProdThreadRunningProcessID,queID));
				jd.hdel(RedisKeys.hashProdThreadRunningProcessID,queID);

				jd.lrem(RedisKeys.listProdThreadRunning, 1, tempkey);
				jd.rpush(RedisKeys.listProdThreadFailed, String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + threadEndTime + "|" + command);
				System.out.println(threadEndTime + " Failed : "+ command);
				// place your code here
			}

		});


	}

	@Override
	public void run() {
		//System.out.println(Thread.currentThread().getName()+' Start. Command = '+command);
		try {
			try {
				processCommand();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		//System.out.println(Thread.currentThread().getName()+' End.');

		Runtime.getRuntime().addShutdownHook(new Thread() {

			@Override
			public void run() {

				RedisVars.redisHost = "localhost";
				final Jedis jd = new Jedis(RedisVars.redisHost);
				System.out.println("Program stoped");
				jd.hset(RedisKeys.hashProdThreadFailedProcessID,queID, getScore(jd,RedisKeys.hashProdThreadRunningProcessID,queID));
				jd.hdel(RedisKeys.hashProdThreadRunningProcessID,queID);

				jd.lrem(RedisKeys.listProdThreadRunning, 1, tempkey);
				jd.rpush(RedisKeys.listProdThreadFailed, String.valueOf(threadProcessID) + "|" + threadStartTime + "|" + threadEndTime + "|" + command);
				System.out.println(threadEndTime + " Failed : "+ command);
				// place your code here
			}

		});

	}


}
